#pragma once

#include "MessageHeader.h"
#include <string>

namespace MessageFramework {

/**
 * @brief 消息签名助手（HMAC-SHA256）
 *
 * 安全机制：
 * 1. 签名内容 = MessageHeader(排除signature字段) + SHA256(Body)
 * 2. 签名算法 = HMAC-SHA256(payload, secretKey)
 * 3. 签名编码 = Hex字符串
 *
 * 防篡改保证：
 * - Header任何字段被修改，签名验证失败
 * - Body内容被修改，哈希不匹配，签名验证失败
 * - 时间窗口验证（默认60秒，防重放攻击）
 */
class SignatureHelper {
public:
    /**
     * @brief 生成消息签名
     *
     * @param header 消息头（会自动填充signature字段）
     * @param body 消息体
     * @param secretKey 密钥
     * @return 签名字符串（Hex编码）
     */
    static std::string sign(MessageHeader& header, const std::string& body, const std::string& secretKey);

    /**
     * @brief 验证消息签名
     *
     * @param header 消息头
     * @param body 消息体
     * @param secretKey 密钥
     * @param timeWindowSeconds 时间窗口（秒，0表示不验证时间）
     * @return true=签名有效，false=签名无效或过期
     */
    static bool verify(const MessageHeader& header, const std::string& body,
                       const std::string& secretKey, int timeWindowSeconds = 60);

    /**
     * @brief 计算消息体的SHA256哈希
     *
     * @param body 消息体
     * @return 哈希值（Hex编码）
     */
    static std::string hashBody(const std::string& body);

    /**
     * @brief 生成用于签名的载荷（Payload）
     *
     * 载荷格式：Header(JSON, 排除signature) + "|" + SHA256(Body)
     *
     * @param header 消息头
     * @param bodyHash 消息体哈希
     * @return 载荷字符串
     */
    static std::string generatePayload(const MessageHeader& header, const std::string& bodyHash);

private:
    /**
     * @brief HMAC-SHA256计算
     *
     * @param data 待签名数据
     * @param key 密钥
     * @return HMAC值（Hex编码）
     */
    static std::string hmacSha256(const std::string& data, const std::string& key);

    /**
     * @brief SHA256哈希计算
     *
     * @param data 待哈希数据
     * @return 哈希值（Hex编码）
     */
    static std::string sha256(const std::string& data);

    /**
     * @brief 序列化Header用于签名（排除signature字段）
     */
    static std::string serializeHeaderForSignature(const MessageHeader& header);
};

} // namespace MessageFramework
